package com.twetec.cms.adapter.pc.backend.interceptor;

import com.fasterxml.jackson.databind.DeserializationFeature;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.SerializationFeature;
import com.twetec.cms.adapter.pc.backend.response.R;
import com.twetec.cms.common.constant.RedisConst;
import com.twetec.cms.common.util.jwt.JWTUtil;
import com.twetec.cms.common.util.cache.RedisCache;
import com.twetec.cms.model.vo.system.PermissionVO;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.web.servlet.handler.HandlerInterceptorAdapter;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.PrintWriter;
import java.util.List;

/**
 * 拦截器-用户权限检查
 */
@Component
public class AuthorizationInterceptor extends HandlerInterceptorAdapter {

    private static final Logger logger = LoggerFactory.getLogger(AuthorizationInterceptor.class);

    @Autowired
    private RedisCache redisCache;

    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {

        // 在这里需要根据用户的id,验证该用户是否有当前路由的访问权限,如果没有，则返回错误，如果有则继续处理
        // 注意，这里的读取，都是从redis缓存中读取，权限数据，由用户登录成功时，一并更新

//         从http头中获取Authorization
        String authorization = request.getHeader("Authorization");
        // 如果authorization存在，则解析出jwt
        String jwt = StringUtils.substringAfter(authorization, "Bearer ");

        Long userId = JWTUtil.parseUserId(jwt);
        if (userId <= 0) {
            response(response, R.failureUserAuth().msg("用户身份无效，请重新登录"));
            return false;
        }

        logger.info(String.valueOf(userId));

        // 1.获取当前访问的url
        String httpPath = request.getRequestURI();
        System.out.println("httpPath" + httpPath);

        // 2.获取权限列表
        List<PermissionVO> list = redisCache.getList(RedisConst.REDISKEY_PERMISSION_LIST + userId);

        System.out.println("获取权限列表" + list);

        // 3.判断是否存在该权限
        boolean contains = false;
        for (PermissionVO permissionVO : list) {
            if (permissionVO.getHttpPath() == null) { continue; }
            if ((permissionVO.getHttpPath().trim()).equals(httpPath)) {
                contains = true;
                break;
            }
        }

        System.out.println("是否存在该权限" + contains);

        // 不存在
        if (!contains) {
            response(response, R.failureUserAuth().msg("权限校验失败 !!!"));
            return false;
        }

        return true;
    }

    private void response(HttpServletResponse response, R r) throws Exception {
        response.setContentType("application/json; charset=utf-8");

        ObjectMapper objectMapper = new ObjectMapper();
        objectMapper.enable(SerializationFeature.INDENT_OUTPUT);
        objectMapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);

        String rJSONStr = objectMapper.writeValueAsString(r);

        PrintWriter printWriter = response.getWriter();
        printWriter.print(rJSONStr);
        printWriter.close();

        response.flushBuffer();
    }

}
